package com.jlf.starter.logger.reactive.entity;

import com.jlf.tool.clock.SystemClock;
import lombok.Getter;
import lombok.Setter;
import org.springframework.web.server.ServerWebExchange;

import java.net.InetSocketAddress;
import java.time.LocalDateTime;
import java.util.List;
import java.util.Map;

/**
 * 日志对象封装
 *
 * @author wujr
 * 2023/8/3
 * @version 1.0
 * 【变更历史】
 * [wujr 2023/8/3 1.0 新增]
 */
@Getter
@Setter
public class LogObject {
    /**
     * 跟踪的请求id
     */
    private String traceId;
    private String host;
    private Integer port;
    /**
     * 请求的方法
     */
    private String method;
    /**
     * 请求的地址
     */
    private String uri;
    private String localIp;
    private String remoteIp;
    /**
     * 接收到请求的毫秒时戳
     */
    private Long requestMillis;
    /**
     * 接收到请求的时间
     */
    private LocalDateTime requestTime;
    /**
     * 处理请求后输出响应结果的时间
     */
    private LocalDateTime responseTime;
    /**
     * 本次请求的耗时，毫秒
     */
    private Long timeElapsed;
    /**
     * 头部参数
     */
    private Map<String, List<String>> headers;
    /**
     * 请求的内容
     */
    private Object requestBody;
    /**
     * 请求的内容的长度
     */
    private long bodyLength;
    /**
     * 请求的参数
     */
    private Map<String, List<Object>> params;
    /**
     * 这是响应的结果内容
     */
    private Object responseBody;
    /**
     * 错误码
     */
    private Integer code;

    public LogObject(ServerWebExchange exchange){
        this.host = exchange.getRequest().getURI().getHost();
        this.port = exchange.getRequest().getURI().getPort();
        this.requestTime = LocalDateTime.now();
        this.requestMillis = SystemClock.now();
        this.method = exchange.getRequest().getMethod().name();
        this.uri = exchange.getRequest().getURI().getPath();
        this.traceId = exchange.getRequest().getId();
        this.bodyLength = exchange.getRequest().getHeaders().getContentLength();
        InetSocketAddress socketAddress = exchange.getRequest().getLocalAddress();
        if (socketAddress != null){
            this.localIp = socketAddress.toString();
        }else{
            this.localIp = "unknown";
        }
        socketAddress = exchange.getRequest().getRemoteAddress();
        if (socketAddress != null){
            this.remoteIp = socketAddress.toString();
        }else{
            this.remoteIp = "unknown";
        }
    }

    public boolean hasBody(){
        return bodyLength > 0;
    }
}
